Javascript Jems - Active Logic, Truthy and Falsey |
Written by Ian Elliot | |||||||||||||||||||||||||||||||||||||||||||||||||
Thursday, 29 November 2018 | |||||||||||||||||||||||||||||||||||||||||||||||||
Page 1 of 3 JavaScript takes an interesting view of logic, the way that it is implemented and what sorts of use you can put it to. Instead of just thinking about And and Or as logic tables you can think of them as variations on the procedural if..then..else. So if you don't know about the active approach to logic - read on.
Now available as a book from your local Amazon.JavaScript Jems:
|
A | B | A||B |
F | F | F |
F | T | T |
T | F | T |
T | T | T |
with T=true and F=false.
If you try this out using:
A=true;
B=false;
if(A||B) alert("The expression is TRUE");
you will see that the result is indeed true as the line starting T,F suggests.
Notice that thinking about logical operations as truth tables makes them seem somehow static - and certainly not part of the flow of control of a program. However this is just an illusion. Logic functions and branching of the flow of control are deeply related - so much so that they are the same thing.
The first difference between JavaScript and other languages is the fact that it uses a concept of "truthiness" and "falsiness".
All values in JavaScript can be treated as if they were Boolean values.
The values zero, null, undefined and the null string are falsey and they behave in logical expressions as if they were false.
Everything else is truthy and they behave in logical expressions as if they were true.
So for example you can write
A=20;
B=null;
if(A||B) alert("The expression is TRUE");
and still see the TRUE message displayed because A is set to a truthy value and B is set to a falsey value which results in a truthy value.
Active Logic
However things are even stranger than just truthy and falsey values. There is another way to interpret Boolean logic that gets closer to the active or procedural notion of programming.
Take a look at the logical table for OR again:
A | B | A||B |
F | F | F |
F | T | T |
T | F | T |
T | T | T |
You could interpret it as saying
"return the first value if it is true and return the second value otherwise".
In more usual programming terms:
if A then A else B
or as a JavaScript function
function or(A,B){
if(A) {
return A;
}else{
return B;
}
}
When you first see this form of the OR truth table it comes as something of a shock.
We are so familiar with thinking of logical operators as just that - operators - that to see OR expressed in "if then else" form is almost disturbing. However you can't object as it really does work - try it out and see.
This rule gives you exactly the same truth table when the values are Boolean but consider what you get if the first value is numeric with 0 i.e. falsey and 20 i.e. truthy and the second is a string with "" and "Hello" being falsey and truthy respectively:
A | B | A||B |
0 | "" | "" |
0 | "Hello" | "Hello" |
20 | "" | 20 |
20 | "Hello" | 20 |
This looks very strange but you can see that A||B returns B if A is falsey and A if A is truthy.
Using the if statement equivalent of A||B makes what is happening clear:
result=A||B;
is the same as
if(A){
result=A
}else{
result=B
};
For example:
A=2*6+9;
B=null;
alert(A || B);
displays 21 because the first variable is truthy but:
A=null;
B="hello";
alert(A || B);
displays "hello" because A is falsey.
This last example also gives us some idea of what this could be use for - default values. For example, consider the following function:
function test(a){
a=a||"default value";
alert(a);
}
If you don't remember to, or don't want to, set the a parameter then it is undefined when the function starts to run and hence it is falsey and a is set to "default value". That is:
test();
results in "default value" being displayed. If you set the parameter then it is a truthy value and a remains unchanged. Notice however that if you pass in a falsey value such as the null string "" or 0 then these will also be replaced by the default value which might not be not what you intended.
<ASIN:1871962579>
<ASIN:0137054890>
<ASIN:0470526912>
<ASIN:1449381871>